package one.stand.controller.home;

import com.jmp.api.dto.*;
import com.jmp.autocofiguration.web.interceptor.SecurityAuthCheck;
import com.jmp.base.dto.*;
import com.jmp.feign.*;
import com.jmp.service.api.admin.BannerApi;
import com.jmp.service.api.admin.dto.BannerListDto;
import com.jmp.service.api.admin.dto.BannerListVo;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import one.stand.advice.ResultEnum;
import one.stand.dto.ConvertUtils;
import one.stand.dto.DictDto;
import one.stand.dto.UserDto;
import one.stand.model.BusinessCard;
import one.stand.model.ResultModel;
import one.stand.response.LoginResponse;
import one.stand.service.BusinessCardBaseService;
import one.stand.service.sys.SysDictValueService;
import one.stand.service.user.UserAdminService;
import one.stand.util.AssertUtil;
import one.stand.util.DateUtil;
import one.stand.util.RequestContext;
import one.stand.util.RequestContextHolder;
import org.apache.commons.lang3.BooleanUtils;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;

import javax.servlet.http.HttpServletResponse;
import java.text.ParseException;
import java.util.Date;
import java.util.List;
import java.util.Objects;

/**
 * @author Administrator
 */
@Api(description = "登录接口")
@RestController
@RequestMapping("home")
public class HomeController {

    private Date DATE_NEW_USER = DateUtil.format.parse("2020-02-26");

    @Autowired
    private LiveFeign liveFeign;
    @Autowired
    private SmsFeign smsFeign;
    @Autowired
    private SecurityFeign securityFeign;
    @Autowired
    private SecurityUserFeign securityUserFeign;
    @Autowired
    private CompanyFeign companyFeign;
    @Autowired
    private ChatFeign chatFeign;
    @Autowired
    private BannerFeign bannerFeign;
    @Autowired
    private TemplateFeign templateFeign;

    @Autowired
    private BusinessCardBaseService businessCardBaseService;
    @Autowired
    private UserAdminService userAdminService;
    @Autowired
    private SysDictValueService sysDictValueService;

    public HomeController() throws ParseException {
    }

    @ApiOperation(value = "0启动页广告")
    @GetMapping("/ad")
    public ResultModel<HomeAdResponse> ad() {
        BannerListDto bannerListDto = BannerListDto.builder()
                .companyId(BannerApi.COMPANY_ID_PLATFORM)
                .bannerType(BannerApi.BANNER_TYPE_CRM_APP)
                .refId(null)
                .build();
        bannerListDto.setAll();
        ResultModel<BannerListVo> bannerListVoResultModel = bannerFeign.list(bannerListDto);
        AssertUtil.isTrue(bannerListVoResultModel);
        List<HomeAdResponse.Banner> adList = ConvertUtils.list(bannerListVoResultModel.getData().getBannerPage().getList(), companyBanner -> {
            return HomeAdResponse.Banner.builder()
                    .bannerId(companyBanner.getId())
                    .source(companyBanner.getSource())
                    .event(companyBanner.getEvent())
                    .eventId(companyBanner.getEventId())
                    .memo(companyBanner.getMemo())
                    .sizeRate(companyBanner.getSizeRate())
                    .build();
        });

        loadTemplates();

        HomeAdResponse response = HomeAdResponse.builder()
                .adList(adList)
                .build();
        return ResultModel.success(response);
    }

    @ApiOperation(value = "0配置")
    @GetMapping("/config")
    public ResultModel<HomeConfigResponse> config() {

        boolean openLive = sysDictValueService.isOn(SysDictValueService.Type.LIVE_OPEN, "APP");
        DictDto ticketShowType = sysDictValueService.get2(SysDictValueService.Type.CRM_APP, "TICKET_SHOW");

        HomeConfigResponse response = HomeConfigResponse.builder()
                .openLive(BooleanUtils.toInteger(openLive))
                .ticketShowType(ticketShowType.getValueInteger(1))
                .build();
        return ResultModel.success(response);
    }

    @ApiOperation(value = "1用户名密码登录")
    @PostMapping("/login/pwd")
    public ResultModel<HomeLoginResponse> loginPwd(@RequestAttribute HomeLoginPwdRequest request, HttpServletResponse response) {
        SecurityLoginCrmApiPasswordRequest loginPwdRequest = SecurityLoginCrmApiPasswordRequest.builder()
                .companyKey(request.getCompanyKey())
                .username(request.getUsername())
                .password(request.getPassword())
                .build();
        ResultModel<LoginResponse> model = securityFeign.loginCrmApiPassword(loginPwdRequest);
        AssertUtil.isTrue(model);
        HomeLoginResponse loginResponse = getResponse(model.getData(), response);
        return ResultModel.success(loginResponse);
    }

    @ApiOperation(value = "2短信验证码发送(新,4位)")
    @PostMapping("sms2")
    public ResultModel sendSms2(@RequestAttribute HomeSendSmsRequest request) {
        RequestContext.Request requestContext = RequestContextHolder.getRequestContext().getRequest();
        SmsCaptchaRequest captchaRequest = SmsCaptchaRequest.builder()
                .phone(request.getPhone())
                .type(SmsCodeEnums.login_sms.getCode())
                .ip(requestContext.getIp())
                .length(4)
                .build();
        ResultModel resultModel = smsFeign.captchaSend(captchaRequest);
        AssertUtil.isTrue(resultModel);
        return ResultModel.success();
    }

    @ApiOperation(value = "2短信登录")
    @PostMapping("/sms/login")
    public ResultModel<HomeLoginResponse> loginSms(@RequestAttribute HomeLoginSmsRequest request, HttpServletResponse response) {
        SecurityLoginCrmApiPasswordRequest loginPwdRequest = SecurityLoginCrmApiPasswordRequest.builder()
                .companyKey(request.getCompanyKey())
                .username(request.getUsername())
                .password(request.getPassword())
                .pushCid(request.getClientId())
                .clientEnum(ClientEnum.CRM_APP)
                .build();
        ResultModel<LoginResponse> model = securityFeign.loginCrmAppSms(loginPwdRequest);
        AssertUtil.isTrue(model);
        HomeLoginResponse loginResponse = getResponse(model.getData(), response);
        return ResultModel.success(loginResponse);
    }

    @ApiOperation(value = "3微信登陆接口2(APP登录)")
    @PostMapping("/login/wx")
    public ResultModel<HomeLoginResponse> loginWx(@RequestAttribute HomeLoginWxRequest request, HttpServletResponse response) {
        RequestContext.Request requestContext = RequestContextHolder.getRequestContext().getRequest();

        SecurityLoginCrmApiWx2Request securityLoginCrmApiWxRequest = SecurityLoginCrmApiWx2Request.builder()
                .companyKey(requestContext.getCompanyKey())
                .code(request.getCode())
                .clientId(request.getClientId())
                .clientEnum(ClientEnum.CRM_APP)
                .build();
        ResultModel<LoginResponse> model = securityFeign.loginCrmApiWx2(securityLoginCrmApiWxRequest);
        AssertUtil.isTrue(model);
        HomeLoginResponse loginResponse = getResponse(model.getData(), response);
        return ResultModel.success(loginResponse);
    }

    @ApiOperation(value = "4绑定手机号")
    @PostMapping("/bind/tel")
    @SecurityAuthCheck(checkPhone = false)
    public ResultModel bindTel(@RequestAttribute HomeBindTelRequest request) {
        SmsCaptchaCheckRequest smsCaptchaCheckRequest = SmsCaptchaCheckRequest.builder()
                .phone(request.getPhone())
                .captcha(request.getSmsCode())
                .type(SmsCodeEnums.login_sms.getCode())
                .build();
        ResultModel<SmsCaptchaCheckResponse> resultModel = smsFeign.captchaCheck(smsCaptchaCheckRequest);
        AssertUtil.isTrue(resultModel);
        AssertUtil.isTrue(resultModel.getData().isSuccess(), ResultEnum.PARAM_CHECK, "验证码错误");
        RequestContext.User optUser = RequestContextHolder.getRequestContext().getUser();
        SecurityUserBindPhoneRequest bindPhoneRequest = SecurityUserBindPhoneRequest.builder()
                .phone(request.getPhone())
                .userId(optUser.getUserId())
                .build();
        AssertUtil.isTrue(securityUserFeign.userBindPhone(bindPhoneRequest));
        return ResultModel.success();
    }

    @PostMapping("/bind/wx2")
    @ApiOperation(value = "4绑定微信(APP登录)")
    @SecurityAuthCheck
    public ResultModel bindWx(@RequestAttribute HomeBindWx2Request request) {
        RequestContext.User optUser = RequestContextHolder.getRequestContext().getUser();
        SecurityUserBindWx2Request securityUserBindWxRequest = SecurityUserBindWx2Request.builder()
                .userId(optUser.getUserId())
                .clientEnum(ClientEnum.CRM_APP)
                .code(request.getCode())
                .build();
        ResultModel resultModel = securityUserFeign.userBindWx2(securityUserBindWxRequest);
        AssertUtil.isTrue(resultModel);
        return ResultModel.success();
    }

    private HomeLoginResponse getResponse(LoginResponse loginResponse, HttpServletResponse response) {

        response.setHeader("token", loginResponse.getToken());
        response.setHeader("id", loginResponse.getUserId().toString());

        UserDto user = userAdminService.get(loginResponse.getUserId().intValue());
        final Integer companyId = null;
        boolean hasCard = loginResponse.getCardId() > 0;
        boolean isNewUser = true;
        if (hasCard) {
            BusinessCard businessCard = businessCardBaseService.getCustomer(loginResponse.getCardId());
            isNewUser = businessCard.getCreateTime().after(DATE_NEW_USER);
        }
        boolean authPhone = isNewUser && StringUtils.isBlank(user.getPhone());
        boolean authWx = isNewUser && StringUtils.isBlank(user.getUnionid());

        Integer auditPass;
        if (isNewUser && hasCard) {
            BusinessCard businessCard = businessCardBaseService.getCustomer(loginResponse.getCardId());
            ResultModel<CompanyAuditInfoResponse> companyAuditInfoResponseResultModel = companyFeign.auditInfo(CompanyAuditInfoRequest.builder().companyId(businessCard.getCompanyId()).build());
            AssertUtil.isTrue(companyAuditInfoResponseResultModel);
            auditPass = companyAuditInfoResponseResultModel.getData().getStatus();
        } else if (!isNewUser) {
            auditPass = 1;
        } else {
            auditPass = 2;
        }
        String auditPassMsg = null;
        if (auditPass == 0) {
            auditPassMsg = "您创建的企业在审核中";
        } else if (auditPass == 2) {
            auditPassMsg = "您还未创建名片";
        }

        ResultModel<ChatInfoVo> chatInfoVoResultModel = chatFeign.info(ChatInfoDto.builder().userId(loginResponse.getUserId().intValue()).build());
        String chatUserId = null;
        String chatPassword = null;
        if (chatInfoVoResultModel.isSuccess()) {
            chatUserId = chatInfoVoResultModel.getData().getChatUserId();
            chatPassword = chatInfoVoResultModel.getData().getChatPassword();
        }

        ResultModel<LiveVideoSaveSignVo> videoSaveSignVoResultModel = liveFeign.videoSaveSign(LiveVideoSaveSignDto.builder()
                .userId(user.getUserId())
                .build());
        AssertUtil.isTrue(videoSaveSignVoResultModel);

//        loadTemplates();

        return HomeLoginResponse.builder()
                .token(loginResponse.getToken())
                .userId(loginResponse.getUserId())
                .userName(loginResponse.getUserName())
                .avatarUrl(loginResponse.getAvatarUrl())
                .roleId(loginResponse.getRoleId())
                .ossUrl(loginResponse.getOssUrl())
                .phone(loginResponse.getPhone())
                .cardId(loginResponse.getCardId())
                .companyName(loginResponse.getCompanyName())
                .isAgent(loginResponse.getIsAgent())
                .authPhone(BooleanUtils.toInteger(authPhone))
                .authWx(BooleanUtils.toInteger(authWx))
                .auditPass(auditPass)
                .auditPassMsg(auditPassMsg)

                .chatUserId(chatUserId)
                .chatPassword(chatPassword)

                .videoSign(videoSaveSignVoResultModel.getData().getSign())
                .build();
    }

    private void loadTemplates() {
        final RequestContext.User optUser = RequestContextHolder.getRequestContext().getUser();
        if (Objects.nonNull(optUser) && Objects.nonNull(optUser.getCardId())) {//提前生成海报
            TemplateListDto templateListDto = TemplateListDto.builder()
                    .companyId(optUser.getCompanyId())
                    .cardId(optUser.getCardId())
                    .build();
            templateListDto.setPageInit(1, 10);
            templateFeign.listAsync(templateListDto);
        }
    }
}
